from typing import ByteString
import matplotlib.pyplot as plt
import numpy as np
from targetAlloc import targetalloc


# Initialization the group
# Generate a random matrix in the range of value
popNum = 40
maxgen = 100
# Variability
Variability = 0.2
Crossprobability = 0.8
x_0 = np.random.randint(0,7,size=(popNum,15))

#Calculate population adaptivity value
fitness = targetalloc(x_0)

bestFit = []
bf = 0

for g in range(0,maxgen):

    # 轮盘赌
    Probability = []
    for j in range(0,popNum):
        Probability.append(round(fitness[0,j]/np.sum(fitness[0,:]),5))

    #选择
    newPop = np.empty([popNum,15],dtype=int)
    proSum = 0
    for i in range(0,popNum):
        for j in range(0,popNum):
            proSum += Probability[j]
            c = np.random.rand()
            if proSum > c:
                newPop[i,:] = x_0[j,:]
                break
        proSum = 0

    # 计算新种群的各个个体的适应度值
    newfit = targetalloc(newPop)
    tempPop = newPop
    #交叉
    # print(type(popNum))
    for i in range(0,int(popNum/2)):
        if np.random.rand() < Crossprobability:
            # 交叉点
            posi = np.random.randint(0,14)
            if i == 0:
                newPop[2*i,0:posi] = tempPop[2*i+1,0:posi]
                newPop[2*i+1,posi:] = tempPop[2*i,posi:]
            else:
                newPop[2*i-1,0:posi] = tempPop[2*i,0:posi]
                newPop[2*i,posi:] = tempPop[2*i-1,posi:]
    #变异
    for i in range(0,popNum):
        if np.random.rand() < Variability:
            posi = np.random.randint(0,14)
            newPop[i,posi] = np.random.randint(0,7)
    
    newfit = targetalloc(newPop)

    if np.max(newfit) > bf:
        bf = np.max(newfit)

    bestFit.append(bf)

# Drawing
plt.style.use('ggplot')
fig = plt.figure()
ax = fig.add_subplot(111)

plt.ylabel('Fitness', fontdict={'family' : 'Times New Roman', 'size'   : 16})
plt.xlabel('Evolutionary generation', fontdict={'family' : 'Times New Roman', 'size'   : 16})
plt.yticks(fontproperties = 'Times New Roman', size = 14)
plt.xticks(fontproperties = 'Times New Roman', size = 14)
plt.legend(prop={'family' : 'Times New Roman', 'size'   : 16})

plt.plot(bestFit)
plt.show()
